<!--
 * @Author: zpp
 * @Date: 2023-08-02 15:58:42
 * @LastEditors: zpp
 * @LastEditTime: 2023-08-03 15:43:09
 * @FilePath: \iking-admin-newui\src\MicroApp\views\components\formList.vue
 * @Description: 表单公共组件
-->
<script lang="ts" setup>
import { ref } from 'vue'
interface ItemForm {
  // 表单绑定的值 必填
  key: string
  // 表单显示的类型 必填
  type: string
  // 表单显示的宽度 非必填 默认 6
  span?: number
  // 标签 非必填
  label?: string
  // 标签显示的宽度 非必填 默认 60px
  labelWidth?: string
  // 插槽  处理特殊需求的 非必填
  slotName?: string
  // 拉下，单选框，多选框 的渲染数据 非必填
  options?: any[]
  // 自定义的key
  optionsValue?: string
  // 自定义标签
  optionsLabel?: string
  // 表单要绑定的默认值 非必填
  defaultData?: any
  // 向组件添加element自带的属性、事件 非必填
  // 例 prop: { label: '请选择', clearable: true, change: (e: any) => { console.log(e) }
  props: any
}
// props 类型
interface PropsItem {
  // 表单列表
  formList: ItemForm[]
  // 表单验证
  formRules: object
}
// 父组件传过来的值
const props = withDefaults(defineProps<PropsItem>(), {
  formList: [] as any,
  formRules: {} as any
})

// 表单绑定的值
const formData = ref<any>({})
// 表单添加key和值
if (props.formList && props.formList.length !== 0) {
  props.formList.forEach((element: any) => {
    formData.value[element.key] = element.defaultData ? element.defaultData : ''
  })
}
// 通过ref重置，验证表单数据
const ruleForm = ref<any>(null)
// 向父组件放开属性
defineExpose({
  formData,
  ruleForm
})
</script>

<template>
  <el-form
    v-if="formList && formList.length !== 0"
    ref="ruleForm"
    :model="formData"
    :rules="formRules"
    label-width="80px"
  >
    <el-row style="width: 100%;">
      <el-col v-for="(item, index) in formList" :key="`for${index}`" :span="item?.span || 6">
        <el-form-item :label="item?.label" :label-width="item?.labelWidth || '60px'" :prop="item.key">
          <!-- 插槽 -->
          <template v-if="item?.slotName">
            <slot :name="item?.slotName"></slot>
          </template>
          <!-- 选择器 -->
          <template v-else-if="item?.type === 'el-select'">
            <el-select
              v-model="formData[item?.key]"
              v-bind="item?.props"
              @change="item.props.change($event, item)"
              @clear="item.props.clear($event, item)"
            >
              <el-option
                v-for="options in item?.options"
                :key=" item.optionsValue ? options[item.optionsValue] : options.value"
                :label=" item.optionsLabel ? options[item.optionsLabel] : options.label"
                :value="item.optionsValue ? options[item.optionsValue] : options.value"
              />
            </el-select>
          </template>
          <!-- 单选框 -->
          <template v-else-if="item?.type === 'el-radio'">
            <el-radio-group v-model="formData[item?.key]" v-bind="item?.props" @change="item.props.change($event, item)">
              <el-radio
                v-for="options in item?.options"
                :key="item.optionsValue ? options[item.optionsValue] : options.value"
                :label="item.optionsValue ? options[item.optionsValue] : options.value"
              >
                {{ item.optionsLabel ? options[item.optionsLabel] : options.label }}
              </el-radio>
            </el-radio-group>
          </template>
          <!-- 多选框 -->
          <template v-else-if="item?.type === 'el-checkbox'">
            <el-checkbox-group v-model="formData[item?.key]" v-bind="item?.props" @change="item.props.change($event, item)">
              <el-checkbox
                v-for="options in item?.options"
                :key="item.optionsValue ? options[item.optionsValue] : options.value"
                :label="item.optionsValue ? options[item.optionsValue] : options.value"
              >
                {{ item.optionsLabel ? options[item.optionsLabel] : options.label }}
              </el-checkbox>
            </el-checkbox-group>
          </template>
          <!-- 其他 -->
          <template v-else>
            <component
              :is="item?.type"
              v-model="formData[item?.key]"
              v-bind="item?.props"
              @change="item.props.change($event, item)"
              @blur="item.props.blur($event, item)"
              @focus="item.props.focus($event, item)"
              @click="item.props.click($event, item)"
              @clear="item.props.clear($event, item)"
            />
          </template>
        </el-form-item>
      </el-col>
    </el-row>
  </el-form>
</template>
